﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Practices.Composite.Presentation.Regions;
using Microsoft.Practices.Unity;
using Microsoft.Practices.Composite.Events;
using System.Windows;
using Microsoft.Practices.Composite.Regions;
using System.Windows.Forms.Integration;
using System.Windows.Input;
using System.Windows.Media.Imaging;
using Infrastructure.Aspect.Accessibility;

namespace Infrastructure.WpfClient.Composite.Regions.ModalWindow
{
    public class ModalWindowRegion : Region         
    {
        [Dependency]
        public IUnityContainer Container { get; set; }

        [Dependency]
        public Infrastructure.WpfClient.Session.ISessionService SessionService { get; set; }

        //[Dependency]
        //public Infrastructure.WpfClient.Accessibility.IAccessibilityService AccessibilityService { get; set;}


        private System.Collections.Hashtable _Windows;
        public ModalWindowRegion(IEventAggregator eventAggregator)
        {
            eventAggregator.GetEvent<Infrastructure.WpfClient.GlobalEvents.CloseViewEvent>().Subscribe(Remove);
            this._Windows = new System.Collections.Hashtable();
        }
        public override Microsoft.Practices.Composite.Regions.IRegionManager Add(object view, string viewName, bool createRegionManagerScope)
        {
            IRegionManager manager = createRegionManagerScope ? this.RegionManager.CreateRegionManager() : this.RegionManager;
            this.InnerAdd(view, viewName, manager);
            return manager;
        }
        private void InnerAdd(object view, string viewName, IRegionManager scopedRegionManager)
        {
            if (this.ItemMetadataCollection.FirstOrDefault(x => x.Item == view) != null)
            {
                throw new InvalidOperationException("RegionViewExistsException");
            }
            ItemMetadata itemMetadata = new ItemMetadata(view);
            if (!string.IsNullOrEmpty(viewName))
            {
                if (this.ItemMetadataCollection.FirstOrDefault(x => x.Name == viewName) != null)
                {
                    throw new InvalidOperationException("RegionViewNameExistsException " + viewName);
                }
                itemMetadata.Name = viewName;
            }
            DependencyObject dependencyObject = view as DependencyObject;

            if (dependencyObject != null)
            {
                Microsoft.Practices.Composite.Presentation.Regions.RegionManager.SetRegionManager(dependencyObject, scopedRegionManager);
            }
            this.ItemMetadataCollection.Add(itemMetadata);
        }

        public override void Remove(object view)
        {
            var query = (from c in this.Views where c == view select c).SingleOrDefault();
            if (query != null)
            {
                base.Remove(view);
                if (_Windows.Contains(view.GetHashCode()))
                {
                    var _Window = _Windows[view.GetHashCode()] as Window;
                    _Window.Content = null;
                    _Window.Closed -= _Window_Closed;
                    _Window.SizeChanged -= _Window_SizeChanged;
                    _Window.PreviewKeyDown -= _Window_PreviewKeyDown;
                    _Window.Close();
                    _Windows.Remove(view.GetHashCode());
                }
                if (view is IDisposable) ((IDisposable)view).Dispose();
            }
        }

        public override void Activate(object view)
        {

            var _Window = Container.Resolve<Window>();

            if (view.GetType().GetProperty("Presenter") != null && view.GetType().GetProperty("Presenter").GetValue(view, null) is Infrastructure.WpfClient.Views.Master.MasterPresenter)
            {
                var pre = view.GetType().GetProperty("Presenter").GetValue(view, null) as Infrastructure.WpfClient.Views.Master.MasterPresenter;
                _Window.Title = pre.GetType().GetProperty("TitleView").GetValue(pre, null) as string;
            }

            var personalization = Attribute.GetCustomAttribute(view.GetType(), typeof(ModalWindowsInfoAttribute)) as ModalWindowsInfoAttribute;
            if (personalization != null)
            {
                _Window.WindowState = personalization.State;
                _Window.WindowStartupLocation = personalization.StartupLocation;
                _Window.ResizeMode = personalization.WindowResizeMode;
                _Window.Height = personalization.Height.GetValueOrDefault(_Window.Height);
                _Window.Width = personalization.Width.GetValueOrDefault(_Window.Width);
                _Window.SizeToContent = personalization.SizeToContent;
                _Window.WindowStyle = personalization.WindowStyle;
                if (personalization.ScapeIsExit)
                {
                    _Window.PreviewKeyDown += new System.Windows.Input.KeyEventHandler(_Window_PreviewKeyDown);
                }
            }
            else
            {
                _Window.SizeToContent = SizeToContent.WidthAndHeight;
                _Window.WindowStartupLocation = WindowStartupLocation.CenterScreen;
                _Window.ResizeMode = ResizeMode.NoResize;
            }
            if (view is System.Windows.Forms.UserControl)
            {
                var host = new WindowsFormsHost();
                host.Child = view as System.Windows.Forms.UserControl;
                _Window.Content = host;
            }
            else
            {
                _Window.Content = view;
            }

            _Window.Closed += new EventHandler(_Window_Closed);
            _Window.SizeChanged += new SizeChangedEventHandler(_Window_SizeChanged);
            this._Windows[view.GetHashCode()] = _Window;

            //Acc

            

           // _Window.Height =this.AccessibilityService.getSetting<double>("app", this.SessionService.UserId, view.ToString(), "view", "height", _Window.Height);
           // _Window.Width = this.AccessibilityService.getSetting<double>("app", this.SessionService.UserId, view.ToString(), "view", "width", _Window.Width);



            _Window.Show();

        }

        void _Window_SizeChanged(object sender, SizeChangedEventArgs e)
        {
            
            
            if (e.HeightChanged)
            {
                Window win = sender as Window;
                if (win.Content is System.Windows.Controls.UserControl)
                {
                    var view = win.Content as System.Windows.Controls.UserControl;
                //    this.AccessibilityService.setSetting<double>("app", this.SessionService.UserId, view.ToString(), "view", "height", e.NewSize.Height);
                }


            }
            if (e.WidthChanged)
            {
                Window win = sender as Window;
                if (win.Content is System.Windows.Controls.UserControl)
                {
                    var view = win.Content as System.Windows.Controls.UserControl;
               //     this.AccessibilityService.setSetting<double>("app", this.SessionService.UserId, view.ToString(), "view", "width", e.NewSize.Width);
                }
            }
        }
        void _Window_PreviewKeyDown(object sender, System.Windows.Input.KeyEventArgs e)
        {
            if (e.Key == Key.Escape)
            {
                var win = sender as Window;
                if (win != null)
                {
                    e.Handled = true;
                    win.Close();
                }
            }

        }

        void _Window_Closed(object sender, EventArgs e)
        {
            var win = sender as Window;
            if (win.Content is WindowsFormsHost)
            {
                this.Remove(((WindowsFormsHost)win.Content).Child);
            }
            else
            {
                this.Remove((sender as Window).Content);
            }
        }
    }
}
